home *** CD-ROM | disk | FTP | other *** search
/ MacTech 1 to 12 / MacTech-vol-1-12.toast / Source / MacTech® Magazine / Volume 10 - 1994 / 10.12 Dec 94 / ThreadedSprocket / ExperimentalStuff / MailableWindow.cp < prev    next >
Encoding:
Text File  |  1994-08-26  |  6.1 KB  |  273 lines  |  [TEXT/MMCC]

  1. /*
  2.     File:        MailableWindow.cp
  3.  
  4.     Contains:    A AOCE-aware window base class
  5.                 
  6.     Written by: Dave Falkenburg with help from Steve Falkenburg’s
  7.                 CollaboDraw “object oriented C” sample application.
  8.     
  9.     Copyright:    © 1993-94 by Dave Falkenburg, all rights reserved.
  10.  
  11.     Change History (most recent first):
  12.     
  13.          <2>     8/26/94    DRF        Added AdjustPerfectWindowSizeForMailer.
  14.     To Do:        Just about everything
  15.     
  16.  */
  17.  
  18. #include <Types.h>
  19. #include <OCEStandardMail.h>
  20.  
  21. #include "AppLib.h"
  22. #include "MailableWindow.h"
  23.  
  24.  
  25. TMailableWindow::TMailableWindow()
  26.     {
  27.     //    Remember, we can’t do anything in here because of C++’s insistance
  28.     //    of creating objects from the bottom-up.  If we call CreateWindow in
  29.     //    here then we end up calling the pure-virtual version of MakeNewWindow.
  30.  
  31.     fMailerIsAttached = false;
  32.     fMailerIsExpanded = false;
  33.     }
  34.  
  35.  
  36. TMailableWindow::~TMailableWindow()
  37.     {
  38. #if    qDebug
  39.     //    Release any PowerTalk things if they are still around
  40.  
  41.     if (fMailerIsAttached)
  42.         DebugStr("\pDidn’t call TMailableWindow::Close to dispose mailer");
  43. #endif
  44.     }
  45.  
  46.  
  47. Boolean
  48. TMailableWindow::EventFilter(EventRecord * anEvent)
  49.     {
  50.     if (gHasAOCE)
  51.         {
  52.         SMPMailerResult    whatHappened;
  53.         SMPMailerState    mailerState;
  54.         
  55.         (void) SMPMailerEvent(anEvent,&whatHappened,FrontWindowProcForAOCEUPP,0);
  56.         (void) SMPGetMailerState(fWindow,&mailerState);
  57.  
  58.         //    ALOT MORE STUFF GOES IN HERE!
  59.  
  60.         // track if the mailer has been expanded or contracted        
  61.         if ((whatHappened & kSMPContractedMask) != 0)
  62.             this->ExpandOrContractMailer(false);
  63.         else if ((whatHappened & kSMPExpandedMask) != 0)
  64.             this->ExpandOrContractMailer(true);
  65.  
  66.         // check to see if the app must handle this event
  67.         if ((whatHappened & kSMPAppMustHandleEventMask) != 0)
  68.             return false;
  69.         else
  70.             return true;    //    nope, PowerTalk dealt with the event, we don’t have to.
  71.         }
  72.  
  73.     return false;
  74.     }
  75.  
  76.  
  77. void
  78. TMailableWindow::CreateWindow(WindowType typeOfWindowToCreate /* = kNormalWindow */)
  79.     {
  80. #if    qDebug
  81.     //    You can’t put a mailer in a floating window or a modal window!
  82.  
  83.     if (typeOfWindowToCreate != kNormalWindow)
  84.         DebugStr("\pTMailableWindow: Must be normal windows");
  85. #endif
  86.  
  87.     TWindow::CreateWindow();
  88.     
  89.     if (gHasAOCE && gPreferences.fMailPreferences.fCreateMailerForNewDocuments)
  90.         this->AttachMailerToWindow(true);
  91.  
  92.     fContentRect = fWindow->portRect;
  93.     }
  94.  
  95.  
  96. Boolean
  97. TMailableWindow::Close(void)
  98.     {
  99.     Boolean    reallyClosing = true;
  100.     
  101.     if (fMailerIsAttached)
  102.         {
  103.         //    Offer to send or save the letter if it has changed
  104.  
  105.         }
  106.     else
  107.         {
  108.         //    Offer to save the document if it is dirty
  109.  
  110.         }
  111.  
  112.     if (fMailerIsAttached)
  113.         {
  114.         //    We need to remove the mailer before calling TWindow::Close
  115.         //    otherwise AOCE will get very confused. Too bad they didn’t
  116.         //    integrate better with the window manager to catch this for us.
  117.         
  118.         this->RemoveMailerFromWindow();
  119.         }
  120.  
  121.     if (reallyClosing)
  122.         return TWindow::Close();
  123.  
  124.     return false;
  125.     }
  126.  
  127.  
  128. OSErr
  129. TMailableWindow::AttachMailerToWindow(Boolean createExpanded)
  130.     {
  131.     Point    where = {0,0};
  132.     OSErr    err;
  133.         
  134.     err = SMPNewMailer(fWindow,where,kCanContract,createExpanded,kDefaultAuthIdentity,nil,0L);
  135.     fMailerIsAttached = (err == noErr);
  136.     fMailerIsExpanded = kInitiallyExpanded;
  137.     
  138.     return err;    
  139.     }
  140.  
  141.  
  142. OSErr
  143. TMailableWindow::RemoveMailerFromWindow(void)
  144.     {
  145.     OSErr                err = noErr;
  146.     SMPCloseOptions        closeOptions;
  147.     
  148.     closeOptions.moveToTrash = false;
  149.     closeOptions.addTag = false;
  150.     closeOptions.tag.dataLength = 0;
  151.     
  152.     if (fMailerIsAttached)
  153.         {
  154.         //    Get rid of the PowerTalk mailer header    
  155.         err = SMPDisposeMailer(fWindow,&closeOptions);
  156.         
  157.         fMailerIsAttached = false;
  158.         fContentRect = fWindow->portRect;
  159.         }
  160.         
  161.     return err;
  162.     }
  163.  
  164.  
  165. void
  166. TMailableWindow::Draw(void)
  167.     {
  168.     //    Because of SMPMailerEvent, the PowerTalk mailer, if present will be drawn by AOCE
  169.     //    This means the window’s draw method only needs to worry drawing the other content
  170.  
  171.     RgnHandle    originalClipRgn = NewRgn();
  172.     
  173.     GetClip(originalClipRgn);
  174.     ClipRect(&fContentRect);
  175.  
  176.     //    Possible optimization by checking content rect against visRgn
  177.     //    « we probably also want to do a wacky SetOrigin call here »    
  178.     this->DrawContents();
  179.  
  180.     SetClip(originalClipRgn);
  181.     DisposeRgn(originalClipRgn);
  182.     }
  183.  
  184.  
  185. void
  186. TMailableWindow::AdjustPerfectWindowSizeForMailer(Rect * perfectSize)
  187.     {
  188.     //    If a mailer is attached to the window, figure out how big it is
  189.     //    and make sure that the window is wide enough to deal with it.
  190.  
  191.     if (fMailerIsAttached)
  192.         {
  193.         short    expHeight,contHeight,mWidth;
  194.     
  195.         (void) SMPGetDimensions(&mWidth,&contHeight,&expHeight);    
  196.     
  197.         //    Make sure the perfect size is wide enough for the standard mailer.
  198.     
  199.         if (perfectSize->right < perfectSize->left + mWidth)
  200.             perfectSize->right = perfectSize->left + mWidth;
  201.  
  202.         //    We might also want to adjust height, but for now ignore the problem
  203.         }
  204.     }
  205.     
  206.  
  207. void
  208. TMailableWindow::AdjustForNewWindowSize(Rect * /* oldRect */,Rect * newRect)
  209.     {
  210.     //    NOTE: Assumes rect is always zero-based
  211.  
  212.     fContentRect.bottom = newRect->bottom;
  213.     fContentRect.right = newRect->right;
  214.     }
  215.  
  216.  
  217. void
  218. TMailableWindow::ExpandOrContractMailer(Boolean doExpand)
  219.     {
  220.     GrafPtr    oldPort;
  221.     Rect    prevContentRect, newContentRect;
  222.     short    expHeight,contHeight,mWidth;
  223.  
  224.     GetPort(&oldPort);
  225.     SetPort(fWindow);
  226.     
  227.     (void) SMPGetDimensions(&mWidth,&contHeight,&expHeight);    
  228.  
  229.     prevContentRect = fContentRect;
  230.     newContentRect = fWindow->portRect;
  231.  
  232.     if (doExpand)
  233.         newContentRect.top += expHeight;
  234.     else
  235.         newContentRect.top += contHeight;
  236.  
  237.     this->AdjustForNewContentRect(&prevContentRect,&newContentRect);
  238.     fContentRect = newContentRect;
  239.  
  240.     (void) SMPExpandOrContract(fWindow,doExpand);
  241.     fMailerIsExpanded = true;
  242.  
  243.     SetPort(oldPort);
  244.     }
  245.  
  246.  
  247. void
  248. TMailableWindow::AdjustForNewContentRect(Rect * /* prevContentRect */,Rect * newContentRect)
  249.     {
  250.     //    the default thing to do is to force a complete redraw of the window’s normal
  251.     //    content area. We could be clever and use scrollrect to keep the bits around,
  252.     //    but for now we cheeze out.
  253.     
  254.     InvalRect(newContentRect);
  255.     }
  256.  
  257. void
  258. TMailableWindow::DrawContents(void)
  259.     {
  260.     }
  261.  
  262.  
  263. //    FrontWindow custom procedure for AOCE standard mail package:
  264. //        It enables some of AOCE to cleanly interoperate with “Dean Yu”-style floating windows
  265.  
  266. pascal    WindowPtr
  267. FrontWindowProcForAOCE(long /* unusedParam */)
  268.     {
  269.     return FrontNonFloatingWindow();
  270.     }
  271.  
  272. FrontWindowUPP FrontWindowProcForAOCEUPP = NewFrontWindowProc(&FrontWindowProcForAOCE);
  273.